﻿#region Header
// ------------------------ Licence / Copyright ------------------------
// 
// ScrumTable for Scrum Meeting Support
// Copyright © HSR - Hochschule für Technik Rapperswil
// All Rights Reserved
// 
// Author:
//  Michael Gfeller Silvan Gehrig Patrick Boos
// 
// ---------------------------------------------------------------------
#endregion

#region Usings

using System.Data;
using System.Linq;

using ScrumTable.Common.Data;

#endregion

namespace ScrumTable.Common.Excel.OpenXmlSdk.Extensions
{
    /// <summary>
    /// Provides the additional functionalities required for Excel
    /// data management of a DataTable instance.
    /// </summary>
    public static class DataTableUtil
    {
        #region Properties
        //--------------------------------------------------------------------
        // Properties
        //--------------------------------------------------------------------

        #endregion

        #region Methods
        //--------------------------------------------------------------------
        // Methods
        //--------------------------------------------------------------------

        /// <summary>
        /// Returns true if the current data table contains a row with the given
        /// primary key.
        /// </summary>
        /// <param name="thisPtr">Specifies the pointer to the DataTable instance.</param>
        /// <param name="id">Specifies the id of the row to retrieve.</param>
        /// <returns>Returns true if the given id has been found, otherwise false.</returns>
        public static bool ContainsRow(this DataTable thisPtr, int id)
        {
            if (thisPtr.HasPrimaryKey())
            {
                return (thisPtr.Rows.Find(DataValue.ToValue(id)) != null);
            }
            return false;
        }

        /// <summary>
        /// Tries to retrieve to column with the given id. Calling this
        /// method requires that the current Worksheet accommodates a valid ID column.
        /// </summary>
        /// <param name="thisPtr">Specifies the pointer to the DataTable instance.</param>
        /// <param name="id">Specifies the id of the row to retrieve.</param>
        /// <param name="result">This variable will contain the result value.</param>
        /// <returns>Returns true if the given id has been found, otherwise false.</returns>
        public static bool TryGetRowById(this DataTable thisPtr, int id, out DataRow result)
        {
            result = null;

            if (thisPtr.HasPrimaryKey())
            {
                result = thisPtr.Rows.Find(DataValue.ToValue(id));
                return (result != null);
            }
            return false;
        }

        /// <summary>
        /// Searches for a row entry which contains the specified value in
        /// the first column.
        /// </summary>
        /// <param name="thisPtr">Specifies the pointer to the DataTable instance.</param>
        /// <param name="firstColumnValue">Specifies the first column value to search.</param>
        /// <returns>Returns the first row or a null reference if the row could not be found.</returns>
        public static DataRow SearchForRow(this DataTable thisPtr, string firstColumnValue)
        {
            PreCondition.AssertNotNull(thisPtr, "thisPtr");

            return (from dataRow in thisPtr.GetRows()
                    let dataRowValues = dataRow.GetColumns<DataValue>()
                    where dataRowValues.FirstOrDefault() != null && ObjectUtil.ConvertToString(dataRowValues.First().Value) == firstColumnValue
                    select dataRow).FirstOrDefault();
        }

        internal static DataColumn GetColumn(this DataTable thisPtr, int columnIdx)
        {
            PreCondition.AssertNotNull(thisPtr, "thisPtr");

            for (int i = thisPtr.Columns.Count; columnIdx >= i; ++i)
            {
                DataColumn newColumn = new DataColumn();
                newColumn.DataType = typeof (DataValue);
                newColumn.DefaultValue = DataValue.Empty;
                newColumn.AllowDBNull = false;
                thisPtr.Columns.Add(newColumn);
            }
            return thisPtr.Columns[columnIdx];
        }

        #endregion
    }
}